/**
 * Created by ${PRODUCT_NAME}.
 * User: skylerparr
 * Date: 12/27/10
 * Time: 11:59 AM
 * To change this template use File | Settings | File Templates.
 */
package com.thoughtorigin.asset {
import com.thoughtorigin.loader.AbstractLoader;

import flash.display.Bitmap;
import flash.display.DisplayObject;
import flash.display.Loader;
import flash.display.Sprite;
import flash.events.Event;
import flash.events.IEventDispatcher;
import flash.utils.ByteArray;
import flash.utils.Dictionary;

public class CloningAssetCache implements AssetCache {

    private var _cacheDict: Dictionary;

    public function CloningAssetCache() {
        _cacheDict = new Dictionary(true);
    }

    public function isAssetCached(url:String):Boolean {
        return _cacheDict[url] != null;
    }

    public function cacheAsset(absLoader:AbstractLoader):void {
        if(isAssetCached(absLoader.url)) {
            return;
        }
        var cache: DisplayObject = absLoader.content;

        if(cache is Bitmap) {
            cache = cloneBmp(Bitmap(cache));
            Loader(absLoader.loader).unloadAndStop();
            _cacheDict[absLoader.url] = cache;
        } else {
           cacheSwf(absLoader.url, absLoader.loader, absLoader.contentDispatcher, function(loader: Loader): void {
               absLoader.loader.unloadAndStop();
           });
        }
    }

    private function cacheSwf(url: String, absLoader: Loader, content: IEventDispatcher, callback: Function = null): void {
        var bytes: ByteArray = Object(content).bytes;
        _cacheDict[url] = bytes;
        cloneSwf(bytes, callback);
    }

    private function cloneBmp(bmp: Bitmap): Bitmap {
        return new Bitmap(bmp.bitmapData.clone());
    }

    public function getAsset(url:String, callback: Function):void {
        if(!isAssetCached(url)) {
            callback.call(this, null);
            return;
        }

        if(_cacheDict[url] is Bitmap) {
            callback.call(this, cloneBmp(_cacheDict[url]));
            return
        }

        cloneSwf(_cacheDict[url], function(loader: Loader): void {
            callback.call(this, loader.content);
        })
    }

    private function cloneSwf(bytes: ByteArray, callback: Function): void {
        var loader: Loader = createLoader();
        getLoaderInfo(loader).addEventListener(Event.COMPLETE, function(e: Event): void {
            getLoaderInfo(loader).removeEventListener(Event.COMPLETE, arguments.callee);
            if(callback != null) {
                callback.call(this, loader);
            }
        });
        loader.loadBytes(bytes);
    }

    public function deleteAsset(url:String):void {
        delete _cacheDict[url];
    }

    protected function createLoader(): Loader {
        return new Loader();
    }

    protected function getLoaderInfo(loader: Loader): IEventDispatcher {
        return loader.contentLoaderInfo;
    }
}
}
